package com.zhoug.zmui.dialog;

import android.app.Dialog;
import android.content.Context;
import android.os.Bundle;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.Window;
import android.view.WindowManager;

import com.zhoug.common.utils.LogUtils;
import com.zhoug.common.utils.ResourceUtils;
import com.zhoug.zmui.R;
import com.zhoug.zmui.ZMUIAnimations;
import com.zhoug.zmui.utils.ZMUIConstant;

import androidx.annotation.AttrRes;
import androidx.annotation.LayoutRes;
import androidx.annotation.NonNull;
import androidx.annotation.StyleRes;

/**
 * 所有Dialog的基类
 *
 * @Author 35574
 * @Date 2020/7/21
 * @Description
 */
public abstract class ZMUIDialog extends Dialog {
    private static final String TAG = ">>>ZMUIDialog";
    private static final boolean DEBUG = false;

    /**
     * 宽
     */
    private int width;
    /**
     * 高
     */
    private int height;
    /**
     * 窗口显示的位置,默认居中
     */
    private int gravity;

    /**
     * 窗口动画
     */
    private @StyleRes
    int windowAnimationResId;

    /**
     * 其它标记
     */
    private Object tag;


    public ZMUIDialog(@NonNull Context context) {
        this(context, 0);
    }

    /**
     * @param context    Context
     * @param themeResId 个性化样式 R.style.xxx
     */
    public ZMUIDialog(@NonNull Context context, @StyleRes int themeResId) {
        this(context, themeResId, 0, 0);
    }

    /**
     * @param context      Context
     * @param themeResId   个性化样式 R.style.xxx
     * @param defStyleAttr 全局默认样式R.attr 优先解析这个
     * @param defStyleRes  默认R.style.xxx. defStyleAttr不存在则解析这个
     */
    protected ZMUIDialog(@NonNull Context context, @StyleRes int themeResId, @AttrRes int defStyleAttr, @StyleRes int defStyleRes) {
        super(context, themeResId);
        initialize(context, defStyleAttr, defStyleRes);
    }

    /**
     * 初始化
     * 按需重写
     * 注意:
     * 解析出的属性如果在子类中定义时初始化了,那么解析的值会被定义时的初始化值覆盖
     * 所有属性定义时不要初始化,请在这里初始化
     * @param context
     * @param defStyleAttr 全局默认样式R.attr 优先解析这个
     * @param defStyleRes  默认R.style.xxx defStyleAttr不存在则解析这个
     */
    protected void initialize(@NonNull Context context, @AttrRes int defStyleAttr, @StyleRes int defStyleRes) {
        width = WindowManager.LayoutParams.WRAP_CONTENT;
        height = WindowManager.LayoutParams.WRAP_CONTENT;
        gravity = Gravity.CENTER;
    }

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        requestWindowFeature(Window.FEATURE_NO_TITLE);//必须设置无标题 否则不会匹配内容
        setContentView();
        onViewCreated(savedInstanceState);
        _setAttributes();
        setWindowAnimations(windowAnimationResId);
    }

    protected void setContentView() {
        setContentView(LayoutInflater.from(getContext()).inflate(getLayoutResId(), null));
    }

    /**
     * 布局文件的资源id
     *
     * @return
     */
    protected abstract @LayoutRes
    int getLayoutResId();

    /**
     * 初始化
     */
    protected abstract void onViewCreated(Bundle savedInstanceState);

    /**
     * 设置遮罩
     *
     * @param alpha true: 显示遮罩
     */
    public void setOverlay(boolean alpha) {
        if (getWindow() != null) {
            if (alpha) {
                //主体中配置的默认透明度
                float defDimAmount = ResourceUtils.getAttrFloatValue(getContext(), R.attr.zmui_dimAmount);
                if (defDimAmount<=0) {
                    defDimAmount = ZMUIConstant.DIM_AMOUNT;
                }
                getWindow().setDimAmount(defDimAmount);
            } else {
                getWindow().setDimAmount(0f);

            }
        }
    }

    /**
     * 设置遮罩
     * @param alpha 遮罩透明度 alpha在0.0f到1.0f之间。1.0完全不透明，0.0f完全透明
     */
    public void setOverlay(float alpha) {
        if (getWindow() != null) {
            getWindow().setDimAmount(alpha);
        }
    }

    /**
     * 设置窗口的属性
     */
    protected void _setAttributes() {
        Window window = this.getWindow();
        if (window == null) {
            return;
        }
        WindowManager.LayoutParams attributes = window.getAttributes();
        attributes.width = width;
        attributes.height = height;
        attributes.gravity = gravity;
        if (DEBUG) {
            LogUtils.d(TAG, "_setAttributes:width=" + width + ",height=" + height);
            if (Gravity.CENTER == gravity) {
                LogUtils.d(TAG, "_setAttributes:CENTER");
            } else if (Gravity.BOTTOM == gravity) {
                LogUtils.d(TAG, "_setAttributes:BOTTOM");
            } else {
                LogUtils.d(TAG, "_setAttributes:gravity=" + gravity);
            }
        }
        window.setAttributes(attributes);
    }


    /**
     * 设置窗口的属性
     *
     * @param width   窗口宽 默认{@link WindowManager.LayoutParams#MATCH_PARENT}
     * @param height  高 例：默认{@link WindowManager.LayoutParams#WRAP_CONTENT}
     * @param gravity {@link Gravity} 默认{@link Gravity#CENTER}
     */
    public void setAttributes(int width, int height, int gravity) {
        this.width = width;
        this.height = height;
        this.gravity = gravity;
    }


    /**
     * 窗口的宽
     *
     * @param width 默认{@link WindowManager.LayoutParams#MATCH_PARENT}
     */
    public void setWidth(int width) {
        this.width = width;
    }

    public int getWidth() {
        return width;
    }

    /**
     * 窗口的高
     *
     * @param height 默认{@link WindowManager.LayoutParams#WRAP_CONTENT}
     */
    public void setHeight(int height) {
        this.height = height;
    }

    public int getHeight() {
        return height;
    }

    /**
     * 窗口位置
     *
     * @param gravity {@link Gravity} 默认{@link Gravity#CENTER}
     */
    public void setGravity(int gravity) {
        this.gravity = gravity;
    }

    /**
     * 标记
     *
     * @return 标记
     */
    public Object getTag() {
        return tag;
    }

    /**
     * 标记
     *
     * @param tag 标记
     */
    public void setTag(Object tag) {
        this.tag = tag;
    }


    /**
     * 设置动画
     *
     * @param resId 动画样式id {@link ZMUIAnimations}定义了一些常用动画
     */
    public void setWindowAnimations(@StyleRes int resId) {
        if (resId != 0) {
            windowAnimationResId = resId;
            if (this.getWindow() != null) {
                this.getWindow().setWindowAnimations(resId);
            }
        }

    }

}
